﻿using Pay.Model;
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Dapper;
using Dapper.Contrib.Extensions;

namespace Pay.Dapper
{
   public  class DapperDataAsync
    {
        /// <summary>
        /// 
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="model"></param>
        /// <param name="transaction"></param>
        /// <param name="commandTimeout"></param>
        /// <returns></returns>
        public static async Task<long> InsertAsync<T>(T model, IDbTransaction transaction = null, int? commandTimeout = null) where T : class, IModel, new()
        {
            return await InsertAsync<T, long>(model, transaction, commandTimeout);
        }

        /// <summary>
        /// 
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <typeparam name="TPrimaryKey"></typeparam>
        /// <param name="model"></param>
        /// <param name="transaction"></param>
        /// <param name="commandTimeout"></param>
        /// <returns></returns>
        public static async Task<long> InsertAsync<T, TPrimaryKey>(T model, IDbTransaction transaction = null, int? commandTimeout = null) where T : class, IModel<TPrimaryKey>, new()
        {
            return await InsertAsync<T, TPrimaryKey>(model, ConnectionFactory.GetWriteConnection(), transaction, commandTimeout);
        }

        /// <summary>
        /// 
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <typeparam name="TPrimaryKey"></typeparam>
        /// <param name="model"></param>
        /// <param name="connection"></param>
        /// <param name="transaction"></param>
        /// <param name="commandTimeout"></param>
        /// <returns></returns>
        public static async Task<long> InsertAsync<T, TPrimaryKey>(T model, IDbConnection connection, IDbTransaction transaction = null, int? commandTimeout = null) where T : class, IModel<TPrimaryKey>, new()
        {
            using (connection)
            {
                return await connection.InsertAsync(model, transaction, commandTimeout);
            }
        }

        /// <summary>
        /// 
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="model"></param>
        /// <param name="transaction"></param>
        /// <param name="commandTimeout"></param>
        /// <returns></returns>
        public static async Task<bool> UpdateAsync<T>(T model, IDbTransaction transaction = null, int? commandTimeout = null) where T : class, IModel, new()
        {
            return await UpdateAsync<T, long>(model, transaction, commandTimeout);
        }

        /// <summary>
        /// 
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <typeparam name="TPrimaryKey"></typeparam>
        /// <param name="model"></param>
        /// <param name="transaction"></param>
        /// <param name="commandTimeout"></param>
        /// <returns></returns>
        public static async Task<bool> UpdateAsync<T, TPrimaryKey>(T model, IDbTransaction transaction = null, int? commandTimeout = null) where T : class, IModel<TPrimaryKey>, new()
        {
            using (var conn = ConnectionFactory.GetWriteConnection())
            {
                return await conn.UpdateAsync(model, transaction, commandTimeout);
            }
        }

        /// <summary>
        /// 
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <typeparam name="TPrimaryKey"></typeparam>
        /// <param name="model"></param>
        /// <param name="transaction"></param>
        /// <param name="commandTimeout"></param>
        /// <returns></returns>
        public static async Task<bool> DeleteAsync<T>(T model, IDbTransaction transaction = null, int? commandTimeout = null) where T : class, IModel, new()
        {
            return await DeleteAsync<T, long>(model, transaction, commandTimeout);
        }

        /// <summary>
        /// 
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <typeparam name="TPrimaryKey"></typeparam>
        /// <param name="model"></param>
        /// <param name="transaction"></param>
        /// <param name="commandTimeout"></param>
        /// <returns></returns>
        public static async Task<bool> DeleteAsync<T, TPrimaryKey>(T model, IDbTransaction transaction = null, int? commandTimeout = null) where T : class, IModel<TPrimaryKey>, new()
        {
            using (var conn = ConnectionFactory.GetWriteConnection())
            {

                   
                    return await conn.DeleteAsync(model, transaction, commandTimeout);
            }
        }


    }
}
